package roborally.script.singleCondition;

import roborally.model.Position;
import roborally.model.Robot;
import roborally.script.SingleCondition;
import be.kuleuven.cs.som.annotate.*;
import be.kuleuven.cs.som.taglet.*;

/**
 * @author Joren VERSPEURT
 * @author Mathieu REYMOND
 * @version 3.0
 * 
 * The class representing a CanHitRobot statement in the RoboRally script language.
 */
public class CanHitRobot extends SingleCondition {

	/**
	 * Create a new CanHitRobot condition with a given Robot.
	 * @param robot The Robot this CanHitRobot condition will apply to.
	 */
	public CanHitRobot(Robot robot) {
		super(robot);
	}

	/**
	 * This Condition is true when the closest Element in <code>robot</code>'s direction is a Robot.
	 */
	@Override
	public boolean isTrue() {
		
		boolean result = false;
		Robot closest = null;
		for(Robot r : robot.getBoard().getElements(Robot.class)) {
			if(robot.getPosition().isPlacedAtOrientationOf(r.getPosition(), robot.getOrientation())) {
				if(closest != null) {
					if(robot.getPosition().getManhattanDistance(closest.getPosition()) > robot.getPosition().getManhattanDistance(r.getPosition())) {
						closest = r;
					}
				}
				else {
					result = true;
					closest = r;
				}
			}
		}
		if(result) {
			Position currentPos = robot.getPosition().getNeighbour(robot.getOrientation());
			while(!currentPos.equals(closest.getPosition())) {
				if(robot.getBoard().getElements(currentPos).iterator().hasNext()) {
					result = false;
				}
				currentPos = currentPos.getNeighbour(robot.getOrientation());
			}
		}
		
		
		return result;
	}
	
	/**
	 * The script word for this condition.
	 */
	@Override
	public String toString() {
		return "can-hit-robot";
	}
}
